package com.buddy.java.thread.common;


import com.buddy.java.thread.guarded_suspension.Blocker;
import com.buddy.java.thread.guarded_suspension.ConditionVarBlocker;
import com.buddy.java.thread.guarded_suspension.GuardedAction;
import com.buddy.java.thread.guarded_suspension.Predicate;

import java.util.Timer;
import java.util.TimerTask;
import java.util.concurrent.Callable;

/**
 * 连接告警服务器,并发送告警信息
 */
public class AlarmAgent {
    //用于记录AlarmAgent是否连接上告警服务器
    private volatile boolean connectedToServer = false;

    //模式角色:GuardedSuspension.Predicate
    private final Predicate agentConnected = new Predicate() {
        public boolean evaluate() {
            return connectedToServer;
        }
    };

    //模式角色:GuardedSuspension.Blocker
    private final Blocker blocker = new ConditionVarBlocker();

    //心跳定时器
    private final Timer heartbeatTimer = new Timer(true);

    /**
     * 发送告警信息
     * @param alarm 告警信息
     */
    public void sendAlarm(final AlarmInfo alarm){
        //可能需等待,直到连接上告警服务器
        GuardedAction<Void> guardedAction = new GuardedAction<Void>(agentConnected) {
            //Void限制返回值必须为null
            public Void call() throws Exception {
                doSendAlarm(alarm);
                return null;
            }
        };
    }

    /**
     * 通过网络连接,将告警信息发送给告警服务器
     * @param alarm
     */
    private void doSendAlarm(AlarmInfo alarm) {
        System.out.println("sending alarm"+alarm);
        //模拟发送告警到服务器的耗时
        try{
            Thread.sleep(50);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }


    public void init(){
        //告警服务器连接线程
        Thread connectiongThread = new Thread(new ConnectingTask());
        connectiongThread.start();
        heartbeatTimer.schedule(new HeartbeatTask(),60000,2000);
    }

    public void disconnect() {
        //TODO
        System.out.println("disconnected from alarm server.");
        connectedToServer = false;
    }


    private class ConnectingTask implements Runnable {
        public void run() {
            //TODO

            //模拟连接操作耗时
            try{
                Thread.sleep(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            onConnected();
        }
    }

    private void onConnected() {
        try {
            blocker.singalAfter(new Callable<Boolean>() {
                public Boolean call(){
                    connectedToServer = true;
                    System.out.println("connected to server");
                    return Boolean.TRUE;
                }
            });
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private void onDisconnected() {
        connectedToServer = false;
    }

    private class HeartbeatTask extends TimerTask {
        public void run() {
            //TODO

            if (!testConnection()){
                onDisconnected();
                reconnect();
            }
        }


        private boolean testConnection() {
            //TODO
            return false;
        }


        private void reconnect() {
            ConnectingTask connectingTask = new ConnectingTask();
            //直接在心跳定时器线程中执行
            connectingTask.run();
        }

    }

}
